﻿using ICSharpCode.SharpZipLib.Zip;
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Linq;
using System.Reflection;
using System.Security.Cryptography;
using System.Text;
using System.Xml.Linq;

namespace AutoBackup
{
    internal class Program
    {
        public static readonly string ExecuteDirectory = Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location);
        static void Main(string[] args)
        {
            string now = System.DateTime.Now.ToString("yyyy-MM-dd");
            string aDatabaseDir = @"D:\A_DataBases";
            string targetDir = $"D:\\AutoBackup";
            var beBackupDir = new Dictionary<string, string>()
            {
                {$"{targetDir}\\tiddlywiki\\tiddlywiki{now}.zip", $"{aDatabaseDir}\\tiddlywiki" },
                {$"{targetDir}\\WorkSpace\\WorkSpace{now}.zip", $"{aDatabaseDir}\\WorkSpace" }
            };

            // 备份
            FastZip z = new FastZip();
            z.Password = MD5Encrypt.MD5Encrypt64("yang_genjie@126.com");
            try
            {
                foreach (var item in beBackupDir)
                {
                    var dir = Path.GetDirectoryName(item.Key);
                    if (!Directory.Exists(dir))
                    {
                        Directory.CreateDirectory(dir);
                    }
                    Console.WriteLine($"正在打包：{item.Key},文件来源：{dir}");
                    z.CreateZip(item.Key, item.Value, true, "");
                }

                // 清理五天前的文件
                var autoBackDir = beBackupDir.Select(x => Path.GetDirectoryName(x.Key)).ToList();
                foreach (var dir in autoBackDir)
                {
                    Console.WriteLine(@"正在清理五天前的文件");
                    DeleteOldFiles(Path.GetDirectoryName(dir), 5);
                }
            }
            catch (Exception)
            {
                throw;
            }
        }

        public static void DeleteOldFiles(string dir, int days)
        {
            try
            {
                if (!Directory.Exists(dir) || days < 1) return;

                var now = DateTime.Now;
                foreach (var f in Directory.GetFileSystemEntries(dir).Where(f => File.Exists(f)))
                {
                    var t = File.GetCreationTime(f);
                    var elapsedTicks = now.Ticks - t.Ticks;
                    var elapsedSpan = new TimeSpan(elapsedTicks);

                    if (elapsedSpan.TotalDays > days) File.Delete(f);
                }
            }
            catch (Exception)
            {
                // ignored
            }
        }

        /// <summary>
        /// 执行多条命令
        /// </summary>
        /// <param name="cmds"></param>
        /// <returns></returns>
        public static string RunCmd(List<string> cmds)
        {
            //string strInput = Console.ReadLine();
            using (var p = new Process())
            {
                p.StartInfo.FileName = "cmd.exe";  //设置要启动的应用程序
                p.StartInfo.UseShellExecute = false;//是否使用操作系统shell启动
                p.StartInfo.RedirectStandardInput = true; // 接受来自调用程序的输入信息
                p.StartInfo.RedirectStandardOutput = true;//输出信息
                p.StartInfo.RedirectStandardError = true; // 输出错误
                p.StartInfo.CreateNoWindow = true;  //不显示程序窗口
                p.StartInfo.WindowStyle = ProcessWindowStyle.Normal;

                p.Start(); //启动程序

                foreach (var cmd in cmds)
                {
                    p.StandardInput.WriteLine(cmd);//向cmd窗口发送输入信息
                }

                p.StandardInput.WriteLine("exit"); // 执行完成之后退出窗口
                p.StandardInput.AutoFlush = true;
                string strOuput = p.StandardOutput.ReadToEnd(); //获取输出信息
                p.WaitForExit();//等待程序执行完退出进程
                p.Close();
                return strOuput;
            }
        }
    }

    public class MD5Encrypt
    {
        public static string MD5Encrypt32(string password)
        {
            string cl = password;
            string pwd = "";
            MD5 md5 = MD5.Create();
            byte[] s = md5.ComputeHash(Encoding.UTF8.GetBytes(cl));
            for (int i = 0; i < s.Length; i++)
            {
                pwd = pwd + s[i].ToString("X");
            }
            return pwd;
        }

        public static string MD5Encrypt64(string password)
        {
            string cl = password;
            MD5 md5 = MD5.Create(); //实例化一个md5对像
            byte[] s = md5.ComputeHash(Encoding.UTF8.GetBytes(cl));
            return Convert.ToBase64String(s);
        }
    }
}